package com.binguo.helper;

import com.alibaba.fastjson.JSON;
import com.binguo.common.exception.ServiceException;
import com.binguo.entity.FaceConfidence;
import com.binguo.youtu.Youtu;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import java.io.IOException;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import java.util.ArrayList;
import java.util.List;

import static com.binguo.common.exception.ErrorCode.PERSON_EXISTS;
import static com.binguo.common.exception.ErrorCode.UPLOAD_ERROR;

/**
 * Created by haibang on 18/5/12.
 */
@Component
public class FaceHelper {

    private static Logger logger = LoggerFactory.getLogger(FaceHelper.class);


//    @Value("youtu.appid")
//    private String APP_ID;
//    @Value("youtu.secretID")
//    private String SECRET_ID;
//    @Value("youtu.secretKey")
//    private String SECRET_KEY;
//    @Value("youtu.userId")
//    private String USER_ID;


    private String APP_ID = "10130564";
    private String SECRET_ID = "AKIDuc5KJ2cigQvDH8g9NM7duwiFgsoUF97s";
    private String SECRET_KEY = "g9NM5YliPq1yg9PRFo8CyUkkV1IJ4app";
    private String USER_ID = "3466615736";

    //fixme haibang 1.只能新建一个person，添加该个体的其他图片调用http://api.youtu.qq.com/youtu/api/addface
    //fixme haibang 2.personId 为groupId_customerId,确保唯一性



    /**
     * 创建人脸识别信息
     * personId 为groupId_customerId,确保唯一性
     * @return faceId
     */
    public String newPerson(String url, String personId, String groupId){

        try {
            List<String> groupIds = new ArrayList<>();
            groupIds.add(groupId);
            Youtu faceClient = new Youtu(APP_ID, SECRET_ID, SECRET_KEY,Youtu.API_YOUTU_END_POINT,USER_ID);
            JSONObject object = _handleResponse(faceClient.NewPersonUrl(url,personId,groupIds));
            return (String)object.get("face_id");
        } catch (Exception e) {
            throw new ServiceException(UPLOAD_ERROR);
        }
    }

    /**
     * 人脸识别
     * @return 候选人
     */
    public FaceConfidence faceIdentify(String url, String groupId){
        try {

            Youtu faceClient = new Youtu(APP_ID, SECRET_ID, SECRET_KEY,Youtu.API_YOUTU_END_POINT,USER_ID);
            JSONObject object = _handleResponse(faceClient.FaceIdentifyUrl(url,groupId));
            return JSON.parseObject(object.toString(), FaceConfidence.class);
        } catch (Exception e) {
            throw new ServiceException(UPLOAD_ERROR);
        }
    }

    /**
     *
     * 删除个体
     * @return
     */
    public void deletePerson(String persionId){
        Youtu faceClient = new Youtu(APP_ID, SECRET_ID, SECRET_KEY,Youtu.API_YOUTU_END_POINT,USER_ID);
        try {
            faceClient.DelPerson(persionId);
        } catch (IOException e) {
            e.printStackTrace();
        } catch (KeyManagementException e) {
            e.printStackTrace();
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }

    }

    /**
     *
     * @return
     */
    public Boolean handtracking(String url){
        Youtu faceClient = new Youtu(APP_ID, SECRET_ID, SECRET_KEY,Youtu.API_YOUTU_END_POINT,USER_ID);
        try {
            JSONObject object = faceClient.Handtracking(url);
            HandDTO handDTO =  JSON.parseObject(object.toString(), HandDTO.class);
            return handDTO.getItems()
                    .stream()
                    .findFirst().map(handItemDTO -> "OK".equals(handItemDTO.getLabel())).orElseGet(() ->false);
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }



    private JSONObject _handleResponse(JSONObject response){
        try {
            Integer errorCode = (Integer) response.get("errorcode");
            String errorMsg = (String) response.get("errormsg");
            if(errorCode == 0) {
                return response;
            }else if(errorCode == -1302){
                throw new ServiceException(PERSON_EXISTS);
            } else {
                logger.info("优图response发现错误, errorcode:" + errorCode + ", errormsg: " + errorMsg);
                throw new ServiceException(errorMsg);
            }
        } catch (JSONException e) {
            throw new ServiceException(UPLOAD_ERROR);
        }
    }


    public static void main(String[] args) {
        // y = 0.6x - 30;

        getOtherScore("27", 0, 0);
    }


    public static Double getGenderScore(Integer a, Integer b){
        Double y1 = 0.6 * a - 30;
        Double y2 = 0.6 * b - 30;

        Double score = 30 - Math.abs(y1 + y2);

        if (score > 0) {
            return score;
        } else {
            return 10.0;
        }
    }

    public static Double getBeautyScore(Integer a, Integer b){
        Double y1 = 0.3 * Math.abs(a - b) - 30;
        return Math.abs(y1);
    }

    public static Double getAgeScore(Integer a, Integer genderA, Integer b, Integer genderB){
        Double y1 = null;
        Integer sub;
        if (genderA == 0) {
            sub = b - a;
        } else {
            sub = a - b;
        }

        if (sub >= 5) {
            y1 = (-new Double(30 / 95)) * Math.abs(sub) + new Double(3000 / 95);
        } else if (sub >= 0) {
            y1 = new Double(Math.abs(sub) + 25);
        } else {
            if (Math.abs(sub) <= 10 && Math.abs(sub) >= 0) {
                y1 = 0.5 * Math.abs(b - a) + 25;
            } else {
                y1 = - new Double(1/9) * Math.abs(sub) + new Double(100/9);
            }
        }
        return Math.abs(y1);
    }

    public static Double getOtherScore(String similarity, Integer expA, Integer expB){
        Double score = 0.0;
        Double d = new Double(similarity);
        if (d >= 5.0 && d <= 30.0) {
            score = 0.28 * Math.abs(d) - 0.4;
            System.out.println(score);
        }else{
            score = 2.0;
        }

        score = Math.abs(score);

        Integer sub = Math.abs(expA - expB);

        score += -0.02 * sub + 2;

        return score;
    }


//    public static void main(String[] args) {
//        String url = "http://img.binguoai.com/img_ok_1.jpg";
//        FaceHelper faceHelper = new FaceHelper();
//        JSONObject j = faceHelper.handtracking(url);
//        HandDTO handDTO =  JSON.parseObject(j.toString(), HandDTO.class);
//        Boolean a = handDTO.getItems().stream().findFirst().map(handItemDTO -> "OK".equals(handItemDTO.getLabel())).orElseGet(() ->false);
//        System.out.println(a);
//
//    }
}
